package com.wnxy.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.wnxy.config.AliyunTemplete;
import com.wnxy.dto.*;
import com.wnxy.exception.LoginException;
import com.wnxy.exception.OrderException;
import com.wnxy.exception.RegistertException;
import com.wnxy.model.Manager;
import com.wnxy.mapper.ManagerMapper;
import com.wnxy.model.ManagerRole;
import com.wnxy.service.ManagerRoleService;
import com.wnxy.service.ManagerService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.wnxy.service.RoleService;
import com.wnxy.util.BeanCopyUtil;
import com.wnxy.util.CommonsUtil;
import com.wnxy.util.DateUtil;
import com.wnxy.util.GetRequestUtil;
import com.wnxy.vo.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;

import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.regex.Pattern;
import java.util.stream.Collectors;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author alice
 * @since 2021-10-25
 */
@Service
public class ManagerServiceImpl extends ServiceImpl<ManagerMapper, Manager> implements ManagerService, UserDetailsService {
    @Autowired
    private RedisTemplate<String,Object> rt;
    @Autowired
    private StringRedisTemplate srt;
    @Autowired
    private AliyunTemplete aliyunTemplete;
    @Autowired
    private  PasswordEncoder pe;
    @Autowired
    private ManagerRoleService managerRoleService;
    @Autowired
    private RoleService roleService;

    @Override
    public LoginDto login(Manager manager) {
        Manager one = getOne(new QueryWrapper<Manager>().eq("manager_name", manager.getManagerName()));
        if(null==one) throw new LoginException(201,"用户不存在");
        if (!one.getManagerPassword().equals(manager.getManagerPassword())) throw new LoginException(202, "密码错误");
        one.setManagerLogintime(DateUtil.parseDateLong(System.currentTimeMillis(),"yyyy-MM-dd HH:mm:ss"));
        updateById(one);
        GetRequestUtil.getSession().setAttribute("loginManager",one);//存入账户
        return BeanCopyUtil.copyProperties(one, LoginDto.class);
    }
    @Override
    public LoginDto sendCode(String phone) {
        String s = srt.opsForValue().get("wnxy:theater:manager:" + phone);
        Long time = srt.opsForValue().getOperations().getExpire("wnxy:theater:manager:" + phone);
        if (null!=s) throw new LoginException(StatusCode.LOGINERROR.getCode(), "验证码已发送,"+time+"秒后重置");
        Manager manager = getOne(new QueryWrapper<Manager>().eq("manager_phone", phone));
        if (manager==null) throw new LoginException(StatusCode.LOGINERROR.getCode(), "用户不存在");
        LoginDto loginDto = BeanCopyUtil.copyProperties(manager, LoginDto.class);
        String code = CommonsUtil.getCode(4);
        loginDto.setLoginCode(code);
        System.out.println(code);
        srt.opsForValue().set("wnxy:theater:manager:"+phone,code,60, TimeUnit.SECONDS);
        return loginDto;
    }

    @Override
    public LoginDto loginByPhone(LoginByPhoneVo loginByPhoneVo) throws IllegalAccessException {
        System.out.println(loginByPhoneVo);
        if (!CommonsUtil.hasAllFields(loginByPhoneVo)) throw new LoginException(StatusCode.LOGINERROR.getCode(), "请填写完整信息");
        Manager manager = getOne(new QueryWrapper<Manager>().eq("manager_phone", loginByPhoneVo.getPhone()));
        if (manager==null) throw new LoginException(StatusCode.LOGINERROR.getCode(), "用户不存在");
        String s = srt.opsForValue().get("wnxy:theater:manager:" + loginByPhoneVo.getPhone());
        if (null==s) throw new LoginException(StatusCode.LOGINERROR.getCode(), "验证码无效,请重新发送");
        if(!s.equals(loginByPhoneVo.getLoginCode())) throw new LoginException(StatusCode.LOGINERROR.getCode(), "验证码错误,请重新填写");
        //登陆完成,

        manager.setManagerLogintime(DateUtil.parseDateLong(System.currentTimeMillis(),"yyyy-MM-dd HH:mm:ss"));
        System.out.println(manager);
        updateById(manager);
        GetRequestUtil.getSession().setAttribute("loginManager",manager);//存入账户
        LoginDto loginDto = BeanCopyUtil.copyProperties(manager, LoginDto.class);
        loginDto.setLoginCode(s);
        return loginDto;
    }

    @Override
    public LoginDto saveManager(RegisterVo registerVo) {
        System.out.println(registerVo);
        Boolean flag=false;
        String managerName = registerVo.getManagerName();
        String managerPassword = registerVo.getManagerPassword();
        String managerPhone = registerVo.getManagerPhone();
        String openId = registerVo.getOpenId();
        if(managerName==null) throw new RegistertException(StatusCode.ADDERROR.getCode(), "用户名为空");
        if(managerPhone==null) throw new RegistertException(StatusCode.ADDERROR.getCode(), "电话为空");
        Manager manager = new Manager();
        if(registerVo.getManagerId()==null){
            //注册业务
            if(managerPassword==null) throw new RegistertException(StatusCode.ADDERROR.getCode(), "密码为空");
            managerPassword=pe.encode(managerPassword);
            manager.setManagerPassword(managerPassword);
            manager.setManagerStatus(0);
            manager.setManagerQqName(registerVo.getManagerQqname());
            manager.setManagerRegtime(DateUtil.parseDateLong(System.currentTimeMillis(),"yyyy-MM-dd HH:mm:ss"));
            if (getOne(new QueryWrapper<Manager>().eq("manager_name",managerName))!=null) throw new RegistertException(StatusCode.ADDERROR.getCode(), "用户名已存在");
            if (getOne(new QueryWrapper<Manager>().eq("manager_phone",managerPhone))!=null) throw new RegistertException(StatusCode.ADDERROR.getCode(), "电话已注册");
            if (getOne(new QueryWrapper<Manager>().eq("open_id",openId))!=null) throw new RegistertException(StatusCode.ADDERROR.getCode(), "qq已绑定");
           flag=true;
        }else{
            //更改业务,更改密码和qq另接业务
            manager=getOne(new QueryWrapper<Manager>().eq("manager_name",managerName));
            if (getOne(new QueryWrapper<Manager>().eq("manager_name",managerName))!=null&&!managerName.equals(manager.getManagerName())) throw new RegistertException(StatusCode.ADDERROR.getCode(), "用户名已存在");
            if (getOne(new QueryWrapper<Manager>().eq("manager_phone",managerPhone))!=null&&!managerPhone.equals(manager.getManagerPhone())) throw new RegistertException(StatusCode.ADDERROR.getCode(), "电话已注册");
            openId = manager.getOpenId();
        }
        String regTel = "^1[3-9]\\d{9}$";
        if (!Pattern.matches(regTel, managerPhone)) throw new OrderException(StatusCode.ORDERERROR.getCode(), "请输入可用手机号");
        manager.setManagerName(managerName);
        manager.setManagerPhone(managerPhone);
        manager.setOpenId(openId);
        System.out.println(manager);
        saveOrUpdate(manager);
        //保存角色
        if(flag){
            ManagerRole managerRole = new ManagerRole();
            managerRole.setRoleId(manager.getManagerId());
            managerRole.setRoleId(5);
            managerRoleService.save(managerRole);
        }

        LoginDto loginDto = BeanCopyUtil.copyProperties(manager, LoginDto.class);
        return loginDto;
    }

    @Override
    public PageRoleDto queryManager(QueryPageVo queryPageVo) {
        Page<Manager> page = page(new Page<Manager>(queryPageVo.getCurrent(), queryPageVo.getSize()));
        List<Manager> records = page.getRecords();
        System.out.println(records);
        PageRoleDto pageRoleDto = BeanCopyUtil.copyProperties(page, PageRoleDto.class);
        pageRoleDto.setRecords(BeanCopyUtil.copyList(page.getRecords(),ManagerRoleDto.class));
        return pageRoleDto;
    }

    @Override
    public LoginDto changePhoto(PhotoVo photoVo) {
        System.out.println(photoVo);
        Manager manager = getById(photoVo.getManagerId());
        String oldImg = manager.getManagerImg();
        manager.setManagerImg(photoVo.getManagerImg());
        updateById(manager);
        System.out.println(manager);
//<===删除云文件===>
        String buckName="aliceache";
        if(oldImg!=null&&!"".equals(oldImg)) aliyunTemplete.delete(buckName,oldImg);
        return BeanCopyUtil.copyProperties(manager, LoginDto.class);
    }

    @Override
    public LoginDto qqbind(QQbindVo qqbindvo) {
        Manager manager = getById(qqbindvo.getManagerId());
        manager.setOpenId(qqbindvo.getOpenId());
        manager.setManagerQqName(qqbindvo.getManagerQqName());
        updateById(manager);
        return BeanCopyUtil.copyProperties(manager,LoginDto.class);

    }


    //security验证
    @Override
    public UserDetails loadUserByUsername(String s) throws UsernameNotFoundException {
        Manager one = getOne(new QueryWrapper<Manager>().eq("manager_name",s));
        if(null==one) throw new LoginException(201,"用户不存在");
        ManagerDetail managerDetail = new ManagerDetail();
        ManagerDetail managerDetail1 = BeanCopyUtil.copyProperties(one, ManagerDetail.class);
        Integer roleId = managerRoleService.getOne(new QueryWrapper<ManagerRole>().eq("manager_id", managerDetail1.getManagerId())).getRoleId();
        managerDetail1.setMangerRoleId(roleId);
//        managerDetail.setManagerId(one.getManagerId());
//        managerDetail.setManagerPassword(one.getManagerPassword());
//        managerDetail.setManagerName(one.getManagerName());
//        managerDetail.setManagerImg(one.getManagerImg());

        return managerDetail1;
    }

    @Override
    public void loadManagerRoleSign(ManagerDetail md) {
        RoleServiceImpl roleService = new RoleServiceImpl();
        List<String> roleSign = roleService.getBaseMapper().getRoleSign(md.getManagerId());
    }

    @Override
    public Boolean isRoleSign(Integer managerId, String pathUrl) {
//        String s = getBaseMapper().selectPath(managerId, pathUrl);
//        if(s==null||"".equals(s)) return false;
        return true;
    }

    @Override
    public void loadRolePath() {
        System.out.println(getBaseMapper());
//        List<RolePathDto> rolePathDtos = getBaseMapper().selectPath(managerId);
//        System.out.println(rolePathDtos);

//        Object o = rt.opsForValue().get("wnxy:theater:rolePath:" + rolePathDtos.get(0).getManagerId());
//        List<RolePathDto> rolePathDtosRedis = CommonsUtil.castList(o, RolePathDto.class);
//        if(o==null) rt.opsForValue().set("wnxy:theater:rolePath:"+rolePathDtos.get(0).getManagerId(),rolePathDtos,2,TimeUnit.HOURS);
//        存上所有权限

        List<RolePathDto> rolePathDtosAll = getBaseMapper().selectAllPath();
        Map<Integer, List<RolePathDto>> map = new HashMap<>();
        for (RolePathDto rolePathDto : rolePathDtosAll) {
            if(map.containsKey(rolePathDto.getRoleId())){
                map.get(rolePathDto.getRoleId()).add(rolePathDto);
            }else {
              List<RolePathDto> list = new ArrayList<>();
              list.add(rolePathDto);
              map.put(rolePathDto.getRoleId(),list );
            }
        }
        for (Integer integer : map.keySet()) {
            System.out.println(integer);
            if (rt.opsForValue().get("wnxy:theater:rolePath:"+integer)==null) {
                rt.opsForValue().set("wnxy:theater:rolePath:"+integer,map.get(integer),2,TimeUnit.HOURS);
            }
        }

    }


}

